﻿using JMI_Nucleo.Enumerador;
using JMI_Nucleo.JMIProvider;
using OR.Enumerador;
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Common;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace JMI_Nucleo.Classe
{
    public static class UtilBD
    {
        private static DbType GetTipoBD(object obj)
        {
            Dictionary<Type, DbType> typeMap = new Dictionary<Type, DbType>();
            typeMap[typeof(byte)] = DbType.Byte;
            typeMap[typeof(sbyte)] = DbType.SByte;
            typeMap[typeof(short)] = DbType.Int16;
            typeMap[typeof(ushort)] = DbType.UInt16;
            typeMap[typeof(int)] = DbType.Int32;
            typeMap[typeof(uint)] = DbType.UInt32;
            typeMap[typeof(long)] = DbType.Int64;
            typeMap[typeof(ulong)] = DbType.UInt64;
            typeMap[typeof(float)] = DbType.Single;
            typeMap[typeof(double)] = DbType.Double;
            typeMap[typeof(decimal)] = DbType.Decimal;
            typeMap[typeof(bool)] = DbType.Boolean;
            typeMap[typeof(string)] = DbType.String;
            typeMap[typeof(char)] = DbType.StringFixedLength;
            typeMap[typeof(Guid)] = DbType.Guid;
            typeMap[typeof(DateTime)] = DbType.DateTime;
            typeMap[typeof(DateTimeOffset)] = DbType.DateTimeOffset;
            typeMap[typeof(byte[])] = DbType.Binary;
            typeMap[typeof(byte?)] = DbType.Byte;
            typeMap[typeof(sbyte?)] = DbType.SByte;
            typeMap[typeof(short?)] = DbType.Int16;
            typeMap[typeof(ushort?)] = DbType.UInt16;
            typeMap[typeof(int?)] = DbType.Int32;
            typeMap[typeof(uint?)] = DbType.UInt32;
            typeMap[typeof(long?)] = DbType.Int64;
            typeMap[typeof(ulong?)] = DbType.UInt64;
            typeMap[typeof(float?)] = DbType.Single;
            typeMap[typeof(double?)] = DbType.Double;
            typeMap[typeof(decimal?)] = DbType.Decimal;
            typeMap[typeof(bool?)] = DbType.Boolean;
            typeMap[typeof(char?)] = DbType.StringFixedLength;
            typeMap[typeof(Guid?)] = DbType.Guid;
            typeMap[typeof(DateTime?)] = DbType.DateTime;
            typeMap[typeof(DateTimeOffset?)] = DbType.DateTimeOffset;
            var type = typeMap[obj.GetType()];
            return type;
        }
        
        public static int GetID(DbConnection _conn, string _Tabela, string _Campo, int _Empresa)
        {
            int retorno = 0;
            string cmdSQL = String.Empty;
            DbCommand cmd = null;
            object obj = null;
            bool parar = false;
            int novoID = 0;
            DbDataReader rd = null;

            try
            {
                do
                {
                    cmdSQL = "SELECT MAX(" + _Campo + ") AS PROX_ID FROM " + _Tabela;
                    if (!_Tabela.ToUpper().Equals("CADASTRO.EMPRESA"))
                       cmdSQL += " WHERE empresa = " + _Empresa.ToString();
                    cmd = _conn.CreateCommand();
                    cmd.CommandType = CommandType.Text;
                    cmd.CommandText = cmdSQL;
                    cmd.Prepare();

                    obj = cmd.ExecuteScalar();

                    if (obj == DBNull.Value || Convert.ToInt32(obj) == 0)
                    {
                        retorno = 1;
                        parar = true;
                    }
                    else
                    {
                        novoID = Convert.ToInt32(obj);
                        novoID = novoID + 1;

                        cmdSQL = "SELECT " + _Campo + " FROM " + _Tabela;
                        if (_Tabela.ToUpper().Equals("CADASTRO.EMPRESA"))
                            cmdSQL += " WHERE " + _Campo + " = " + novoID.ToString();
                        else
                            cmdSQL += " WHERE " + _Campo + " = " + novoID.ToString() + " AND empresa = " + _Empresa.ToString();

                        cmd = _conn.CreateCommand();
                        cmd.CommandType = CommandType.Text;
                        cmd.CommandText = cmdSQL;
                        cmd.Prepare();
                        rd = cmd.ExecuteReader(CommandBehavior.Default);

                        if (rd.Read())
                            continue;
                        else
                        {
                            retorno = novoID;
                            parar = true;
                        }

                    }
                } while (parar == false);
            }
            catch (Exception ex)
            {
                #region Grava log local
                mLog _info = new mLog();
                _info._TipoErro = TipoErro.Erro;
                _info.Mensagem = "Erro ao recuperar ID.; " + ex.Message;
                _info.Metodo = "public int GetID(string _Tabela, string _Campo, int _Empresa)";
                _info.StackTrace = ex.StackTrace;
                _info.Tabela = String.Empty;
                LogLocal.Info = _info;
                LogLocal.Gravar();
                #endregion
            }
            finally
            {
                cmd.Dispose();
            }
            return retorno;
        }

        public static void AdicionaParametro(ref DbCommand Comando, string Nome, object Valor)
        {
            DbParameter p = Comando.CreateParameter();
            p.ParameterName = Nome;
            p.Value = Valor;
            Comando.Parameters.Add(p);
        }

        public static object Localiza(string sSelect, object Conteudo, string CampoRetorno, short Empresa)
        {
            DbDataReader rd = null;
            DbCommand _cmd = null;
            DbParameter p = null;
            object retorno = null;
            bool conexaoLocal = false;
            
            try
            {
                if (EngineBD.GetConexao.State == ConnectionState.Closed)
                {
                    EngineBD.Conectar();
                    conexaoLocal = true;
                }
                _cmd = EngineBD.GetConexao.CreateCommand();

                _cmd.CommandType = CommandType.Text;
                _cmd.CommandText = sSelect;

                p = _cmd.CreateParameter();
                p.ParameterName = "@PAR_PESQ";
                p.Value = Conteudo;
                _cmd.Parameters.Add(p);

                p = _cmd.CreateParameter();
                p.ParameterName = "@PAR_EMPRESA";
                p.Value = Empresa;
                _cmd.Parameters.Add(p);

                rd = EngineBD.ExecuteDataReader(_cmd);

                if (rd.Read())
                    retorno = rd[CampoRetorno];
            }
            catch (Exception ex)
            {
                #region Grava log local
                mLog _info = new mLog();
                _info._TipoErro = TipoErro.Erro;
                _info.Mensagem = "Erro ao executar comando. " + ex.Message;
                _info.Metodo = @"public static object Localiza(string sSelect, object Conteudo, string CampoRetorno, short Empresa)";
                _info.StackTrace = ex.StackTrace;
                _info.Tabela = String.Empty;
                LogLocal.Info = _info;
                LogLocal.Gravar();
                #endregion
            }
            finally
            {
                rd.Close();
                if (conexaoLocal)
                    EngineBD.Desconectar();
            }
            if (retorno == null) { retorno = String.Empty; }
            return retorno;
        }        
    }
}
